package com.gugee.ins.common.dal.spider;

import com.gugee.common.exception.BizException;
import com.gugee.ins.common.constant.RedisKeyConst;
import com.gugee.ins.common.dal.spider.config.SpiderConfig;
import com.gugee.ins.common.model.spider.comment.EdgeMediaCommentBody;
import com.gugee.ins.common.model.spider.comment.InsMediaCommentsResponse;
import com.xiguaji.boot.retry.RetryableException;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.retry.annotation.Retryable;
import org.springframework.stereotype.Component;
import org.springframework.web.client.RestTemplate;

import java.util.concurrent.TimeUnit;

/**
 * InsBloggerSpiderClient
 * @author HuangXin
 */
@Slf4j
@Component
public class InsMediaCommentSpiderClient {
    /**
     * restTemplate
     */
    @Autowired
    RestTemplate restTemplate;

    /**
     * redis
     */
    @Autowired
    SpiderConfig spiderConfig;

    /**
     * redis
     */
    @Autowired
    RedisTemplate<String,String> redisTemplate;

    private static final String BIZ_SPIDER_STATUS_ERROR ="BIZ_SPIDER_STATUS_ERROR";
    private static final String URI =". uri:";

    /**
     * 根据uid获取blogger 关注列表
     * @param shortCode
     * @param count
     * @param endCursor
     * @return
     */
    @Retryable(value = RetryableException.class, maxAttemptsExpression = "${ins.spider.insMediaComment.retry:1}")
    public EdgeMediaCommentBody getMediaComments(String shortCode, Integer count, String endCursor) {
        String uri = spiderConfig.getHost() + "/Ins/MediaComments?shortCode={shortCode}";
        if(count != null && count > 0){
            uri += "&count=" + count;
        }
        uri += "&end_cursor={endCursor}";
        spiderSleep(RedisKeyConst.SPIDER_COMMENT,spiderConfig.getSpiderCommentSleepSecond());

        ResponseEntity<InsMediaCommentsResponse> responseEntity = restTemplate.getForEntity(uri, InsMediaCommentsResponse.class, shortCode,endCursor);

        if (responseEntity.getStatusCode() != HttpStatus.OK) {
            throw new BizException(String.format("get ins Media error. status: %s . msg: %s",
                    responseEntity.getStatusCodeValue(), responseEntity.getBody()),BIZ_SPIDER_STATUS_ERROR);
        }
        if (responseEntity.getBody() == null || responseEntity.getBody().getData() == null
                || responseEntity.getBody().getData().getShortCodeMedia() == null
                || responseEntity.getBody().getData().getShortCodeMedia().getEdgeMediaToParentComment() == null) {
            throw new RetryableException("get ins Media error, retry times " + spiderConfig.getSpiderMediaCommentRetryTimes() + URI +
                    uri.replace("{shortCode}", shortCode).replace("{endCursor}",endCursor));
        }
        return responseEntity.getBody().getData().getShortCodeMedia().getEdgeMediaToParentComment();
    }

    /**
     * 爬完就睡眠 防止风控
     */
    private void spiderSleep(String redisKey,long ms){
        if(ms > 0) {
            while (isSleep(redisKey,ms)) {
                //睡眠
                try {
                    Thread.sleep(ms);
                } catch (Exception e) {
                    log.error("spider sleep error,msg:{}",e.getMessage());
                }
            }
        }
    }

    private boolean isSleep(String redisKey,long ms){
        return !redisTemplate.opsForValue().setIfAbsent(redisKey, System.currentTimeMillis() + "", ms, TimeUnit.MILLISECONDS);
    }
}
